// utils/request.js
const app = getApp()

// 基础请求方法
const request = (url, method = 'GET', data = {}, options = {}) => {
  const baseURL = options.baseURL || app.globalData.baseURL
  const showLoading = options.showLoading !== false
  const loadingText = options.loadingText || '加载中...'
  
  // 显示加载状态
  if (showLoading) {
    wx.showLoading({
      title: loadingText,
      mask: true
    })
  }
  
  // 构建请求头
  const header = {
    'Content-Type': 'application/json',
    ...options.header
  }
  
  // 添加认证token
  if (app.globalData.token) {
    header['Authorization'] = `Bearer ${app.globalData.token}`
  }
  
  return new Promise((resolve, reject) => {
    wx.request({
      url: `${baseURL}${url}`,
      method,
      data,
      header,
      timeout: options.timeout || 30000,
      success: (res) => {
        // 隐藏加载状态
        if (showLoading) {
          wx.hideLoading()
        }
        
        if (res.statusCode === 200) {
          resolve(res.data)
        } else if (res.statusCode === 401) {
          // token过期，清除登录状态
          handleTokenExpired()
          reject(new Error('登录已过期，请重新登录'))
        } else if (res.statusCode === 429) {
          wx.showToast({
            title: '请求太频繁',
            icon: 'none'
          })
          reject(new Error('请求太频繁'))
        } else if (res.statusCode >= 500) {
          wx.showToast({
            title: '服务器错误',
            icon: 'none'
          })
          reject(new Error('服务器错误'))
        } else {
          const errorMsg = res.data?.message || '请求失败'
          wx.showToast({
            title: errorMsg,
            icon: 'none'
          })
          reject(new Error(errorMsg))
        }
      },
      fail: (err) => {
        // 隐藏加载状态
        if (showLoading) {
          wx.hideLoading()
        }
        
        console.error('请求失败:', err)
        wx.showToast({
          title: '网络连接失败',
          icon: 'none'
        })
        reject(new Error('网络连接失败'))
      }
    })
  })
}

// GET请求
const get = (url, data = {}, options = {}) => {
  return request(url, 'GET', data, options)
}

// POST请求
const post = (url, data = {}, options = {}) => {
  return request(url, 'POST', data, options)
}

// PUT请求
const put = (url, data = {}, options = {}) => {
  return request(url, 'PUT', data, options)
}

// DELETE请求
const del = (url, data = {}, options = {}) => {
  return request(url, 'DELETE', data, options)
}

// 上传文件
const upload = (url, filePath, formData = {}, options = {}) => {
  const baseURL = options.baseURL || app.globalData.baseURL
  const showLoading = options.showLoading !== false
  const loadingText = options.loadingText || '上传中...'
  
  if (showLoading) {
    wx.showLoading({
      title: loadingText,
      mask: true
    })
  }
  
  const header = {
    ...options.header
  }
  
  if (app.globalData.token) {
    header['Authorization'] = `Bearer ${app.globalData.token}`
  }
  
  return new Promise((resolve, reject) => {
    wx.uploadFile({
      url: `${baseURL}${url}`,
      filePath,
      name: 'file',
      formData,
      header,
      success: (res) => {
        if (showLoading) {
          wx.hideLoading()
        }
        
        try {
          const data = JSON.parse(res.data)
          if (data.code === 200) {
            resolve(data)
          } else {
            wx.showToast({
              title: data.message || '上传失败',
              icon: 'none'
            })
            reject(new Error(data.message || '上传失败'))
          }
        } catch (err) {
          wx.showToast({
            title: '上传失败',
            icon: 'none'
          })
          reject(new Error('上传失败'))
        }
      },
      fail: (err) => {
        if (showLoading) {
          wx.hideLoading()
        }
        
        wx.showToast({
          title: '上传失败',
          icon: 'none'
        })
        reject(new Error('上传失败'))
      }
    })
  })
}

// 处理token过期
const handleTokenExpired = () => {
  app.globalData.token = null
  app.globalData.userInfo = null
  wx.removeStorageSync('token')
  
  wx.showModal({
    title: '登录已过期',
    content: '请重新登录',
    showCancel: false,
    success: () => {
      wx.reLaunch({
        url: '/pages/index/index'
      })
    }
  })
}

// 请求重试
const retry = (fn, maxRetries = 3, delay = 1000) => {
  return new Promise((resolve, reject) => {
    let retries = 0
    
    const attempt = () => {
      fn()
        .then(resolve)
        .catch((err) => {
          retries++
          if (retries < maxRetries) {
            setTimeout(attempt, delay * retries)
          } else {
            reject(err)
          }
        })
    }
    
    attempt()
  })
}

// 请求队列
class RequestQueue {
  constructor(maxConcurrent = 3) {
    this.maxConcurrent = maxConcurrent
    this.currentRequests = 0
    this.queue = []
  }
  
  add(requestFn) {
    return new Promise((resolve, reject) => {
      this.queue.push({ requestFn, resolve, reject })
      this.process()
    })
  }
  
  process() {
    if (this.currentRequests >= this.maxConcurrent || this.queue.length === 0) {
      return
    }
    
    this.currentRequests++
    const { requestFn, resolve, reject } = this.queue.shift()
    
    requestFn()
      .then(resolve)
      .catch(reject)
      .finally(() => {
        this.currentRequests--
        this.process()
      })
  }
}

// 创建请求队列实例
const requestQueue = new RequestQueue()

// 带队列的请求
const queuedRequest = (url, method = 'GET', data = {}, options = {}) => {
  return requestQueue.add(() => request(url, method, data, options))
}

module.exports = {
  request,
  get,
  post,
  put,
  del,
  upload,
  retry,
  queuedRequest,
  RequestQueue
}